home *** CD-ROM | disk | FTP | other *** search
/ Aminet 1 (Walnut Creek) / Aminet - June 1993 [Walnut Creek].iso / aminet / gfx / show / mpeg_player122.lha / amiga / main.c < prev    next >
C/C++ Source or Header  |  1992-12-08  |  11KB  |  536 lines

  1. /*
  2.  * Copyright (c) 1992 The Regents of the University of California.
  3.  * All rights reserved.
  4.  * 
  5.  * Permission to use, copy, modify, and distribute this software and its
  6.  * documentation for any purpose, without fee, and without written agreement is
  7.  * hereby granted, provided that the above copyright notice and the following
  8.  * two paragraphs appear in all copies of this software.
  9.  * 
  10.  * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
  11.  * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT
  12.  * OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF
  13.  * CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  14.  * 
  15.  * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,
  16.  * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
  17.  * AND FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS
  18.  * ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO
  19.  * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
  20.  */
  21. #include "video.h"
  22. #include <sys/types.h>
  23. #include <signal.h>
  24.  
  25. #ifndef AMIGA
  26. #ifndef MIPS
  27. #include <netinet/in.h>
  28. #else
  29. #include <bsd/netinet/in.h>
  30. #endif
  31. #endif
  32.  
  33. #include "util.h"
  34.  
  35. /* Define buffer length. */
  36.  
  37. #define BUF_LENGTH 80000
  38.  
  39. /* Function return type declarations */
  40. void usage();
  41.  
  42. /* External declaration of main decoding call. */
  43.  
  44. extern VidStream *mpegVidRsrc();
  45. extern VidStream *NewVidStream();
  46.  
  47. /* Declaration of global variable to hold dither info. */
  48.  
  49. int ditherType;
  50.  
  51. /* Global file pointer to incoming data. */
  52. FILE *input;
  53.  
  54. /* End of File flag. */
  55. static int EOF_flag = 0;
  56.  
  57. /* Loop flag. */
  58. int loopFlag = 0;
  59.  
  60. /* Shared memory flag. */
  61. int shmemFlag = 0;
  62.  
  63. /* Setjmp/Longjmp env. */
  64. jmp_buf env;
  65.  
  66. #ifdef AMIGA
  67. extern char *amiga_option;
  68. #endif
  69.  
  70.  
  71. /*
  72.  *--------------------------------------------------------------
  73.  *
  74.  * get_more_data --
  75.  *
  76.  *    Called by correct_underflow in bit parsing utilities to
  77.  *      read in more data.
  78.  *
  79.  * Results:
  80.  *    Input buffer updated, buffer length updated.
  81.  *      Returns 1 if data read, 0 if EOF, -1 if error.
  82.  *
  83.  * Side effects:
  84.  *      None.
  85.  *
  86.  *--------------------------------------------------------------
  87.  */
  88.  
  89. int 
  90. get_more_data(buf_start, max_length, length_ptr, buf_ptr)
  91.      unsigned int *buf_start;
  92.      int max_length;
  93.      int *length_ptr;
  94.      unsigned int **buf_ptr;
  95. {
  96.   
  97.   int length, num_read, i, request;
  98.   unsigned char *buffer, *mark;
  99.   unsigned int *lmark;
  100.  
  101.   if (EOF_flag) return 0;
  102.  
  103.   length = *length_ptr;
  104.   buffer = (unsigned char *) *buf_ptr;
  105.  
  106.   if (length > 0) {
  107.     memcpy((unsigned char *) buf_start, buffer, (length*4));
  108.     mark = ((unsigned char *) (buf_start + length));
  109.   }
  110.   else {
  111.     mark = (unsigned char *) buf_start;
  112.     length = 0;
  113.   }
  114.  
  115.   request = (max_length-length)*4;
  116.   
  117.   num_read = fread( mark, 1, request, input);
  118.  
  119.   if (num_read < 0) {
  120.     return -1;
  121.   }
  122.   else if (num_read == 0) {
  123.     *buf_ptr = buf_start;
  124.     
  125.     /* Make 32 bits after end equal to 0 and 32
  126.        bits after that equal to seq end code
  127.        in order to prevent messy data from infinite
  128.        recursion.
  129.     */
  130.  
  131.     *(buf_start + length) = 0x0;
  132.     *(buf_start + length+1) = SEQ_END_CODE;
  133.  
  134.     EOF_flag = 1;
  135.     return 0;
  136.   }
  137.  
  138.   lmark = (unsigned int *) mark;
  139.  
  140.   num_read = num_read/4;
  141.  
  142. #ifndef AMIGA
  143.   for (i=0; i<num_read; i++) {
  144.     *lmark = htonl(*lmark);
  145.     lmark++;
  146.   }
  147. #endif
  148.  
  149.   *buf_ptr = buf_start;
  150.   *length_ptr = length + num_read;
  151.  
  152.   return 1;
  153. }
  154.  
  155. /*
  156.  *--------------------------------------------------------------
  157.  *
  158.  * int_handler --
  159.  *
  160.  *    Handles Cntl-C interupts..
  161.  *
  162.  * Results:
  163.  *    None.
  164.  *
  165.  * Side effects:
  166.  *    None.
  167.  *
  168.  *--------------------------------------------------------------
  169.  */
  170. void
  171. int_handler()
  172. {
  173.   fprintf(stderr, "Interrupted!\n");
  174.   if (curVidStream != NULL)
  175.     DestroyVidStream(curVidStream);
  176.   exit(1);
  177. }
  178.  
  179.  
  180. /*
  181.  *--------------------------------------------------------------
  182.  *
  183.  * main --
  184.  *
  185.  *    Parses command line, starts decoding and displaying.
  186.  *
  187.  * Results:
  188.  *    None.
  189.  *
  190.  * Side effects:
  191.  *    None.
  192.  *
  193.  *--------------------------------------------------------------
  194.  */
  195.  
  196. void
  197. main(argc, argv)
  198.      int argc;
  199.      char **argv;
  200. {
  201.  
  202.   static VidStream *theStream;
  203.   int mark;
  204.   int i;
  205.  
  206.   mark = 1;
  207.   argc--;
  208.  
  209.   input = stdin;
  210.   ditherType = ORDERED_DITHER;
  211.  
  212. #ifdef SH_MEM
  213.   shmemFlag = 1;
  214. #endif
  215.  
  216.   while (argc) {
  217.     if (strcmp(argv[mark], "-nop") == 0) {
  218.       TogglePFlag();
  219.       argc--; mark++;
  220.     } else if (strcmp(argv[mark], "-nob") == 0) {
  221.       ToggleBFlag();
  222.       argc--; mark++;
  223.     } else if (strcmp(argv[mark], "-dither") == 0) {
  224.       argc--; mark++;
  225.       if (argc < 1) {
  226.     perror("Must specify dither option after -dither flag");
  227.     usage(argv[0]);
  228.       }
  229.       if (strcmp(argv[mark], "hybrid") == 0) {
  230.     argc--; mark++;
  231.     ditherType = HYBRID_DITHER;
  232.       } else if (strcmp(argv[mark], "hybrid2") == 0) {
  233.     argc--; mark++;
  234.     ditherType = HYBRID2_DITHER;
  235.       } else if (strcmp(argv[mark], "fs4") == 0) {
  236.     argc--; mark++;
  237.     ditherType = FS4_DITHER;
  238.       } else if (strcmp(argv[mark], "fs2") == 0) {
  239.     argc--; mark++;
  240.     ditherType = FS2_DITHER;
  241.       } else if (strcmp(argv[mark], "fs2fast") == 0) {
  242.     argc--; mark++;
  243.     ditherType = FS2FAST_DITHER;
  244.       } else if (strcmp(argv[mark], "hybrid2") == 0) {
  245.     argc--; mark++;
  246.     ditherType = HYBRID2_DITHER;
  247.       } else if (strcmp(argv[mark], "2x2") == 0) {
  248.     argc--; mark++;
  249.     ditherType = Twox2_DITHER;
  250.       } else if (strcmp(argv[mark], "gray") == 0) {
  251.     argc--; mark++;
  252.     ditherType = GRAY_DITHER;
  253.       } else if (strcmp(argv[mark], "color") == 0) {
  254.     argc--; mark++;
  255.     ditherType = FULL_COLOR_DITHER;
  256.       } else if (strcmp(argv[mark], "none") == 0) {
  257.     argc--; mark++;
  258.     ditherType = NO_DITHER;
  259.       } else if (strcmp(argv[mark], "ordered") == 0) {
  260.     argc--; mark++;
  261.     ditherType = ORDERED_DITHER;
  262.       } else if (strcmp(argv[mark], "mono") == 0) {
  263.     argc--; mark++;
  264.     ditherType = MONO_DITHER;
  265.       } else if (strcmp(argv[mark], "threshold") == 0) {
  266.     argc--; mark++;
  267.     ditherType = MONO_THRESHOLD;
  268.       } else {
  269.     perror("Illegal dither option.");
  270.     usage(argv[0]);
  271.       }
  272.     } 
  273.     else if (strcmp(argv[mark], "-eachstat") == 0) {
  274.       argc--; mark++;
  275. #ifdef ANALYSIS
  276.       showEachFlag = 1;
  277. #else
  278.       fprintf(stderr, "To use -eachstat, recompile with -DANALYSIS in CFLAGS\n");
  279.       exit(1);
  280. #endif
  281.     }
  282.     else if (strcmp(argv[mark], "-shmem_off") == 0) {
  283.       argc--; mark++;
  284.       shmemFlag = 0;
  285.     }
  286.     else if (strcmp(argv[mark], "-loop") == 0) {
  287.       argc--; mark++;
  288.       loopFlag = 1;
  289.     }
  290. #ifdef AMIGA
  291.     else if (strcmp(argv[mark], "-amiga") == 0) {
  292.       argc--; mark++;
  293.       amiga_option = argv[mark];
  294.       argc--; mark++;
  295.     }
  296. #endif
  297.     else if (argv[mark][0] == '-') {
  298.       fprintf(stderr, "Un-recognized flag %s\n",argv[mark]);
  299.       usage(argv[0]);
  300.     }
  301.     else {
  302.       input = fopen(argv[mark], "r");
  303.       if (input == NULL) {
  304.     fprintf(stderr, "Could not open file %s\n", argv[mark]);
  305.     usage(argv[0]);
  306.       }
  307.       argc--; mark++;
  308.     }
  309.   }
  310.  
  311.   signal(SIGINT, int_handler);
  312.  
  313.   init_tables();
  314.   
  315.   switch (ditherType) {
  316.     
  317.   case HYBRID_DITHER:
  318.     
  319.     InitColor();
  320.     InitHybridDither();
  321.     InitDisplay();
  322.     break;
  323.     
  324.     case HYBRID2_DITHER:
  325.     InitColor();
  326.     InitHybridErrorDither();
  327.     InitDisplay();
  328.     break;
  329.     
  330.   case FS4_DITHER:
  331.     InitColor();
  332.     InitFS4Dither();
  333.       InitDisplay();
  334.     break;
  335.     
  336.   case FS2_DITHER:
  337.     InitColor();
  338.     InitFS2Dither();
  339.     InitDisplay();
  340.     break;
  341.     
  342.   case FS2FAST_DITHER:
  343.     InitColor();
  344.     InitFS2FastDither();
  345.     InitDisplay();
  346.     break;
  347.     
  348.   case Twox2_DITHER:
  349.     InitColor();
  350.     Init2x2Dither();
  351.     InitDisplay();
  352.     PostInit2x2Dither();
  353.     break;
  354.  
  355.   case GRAY_DITHER:
  356.     InitGrayDisplay();
  357.     break;
  358.  
  359.   case FULL_COLOR_DITHER:
  360.     InitColorDither();
  361.     InitColorDisplay();
  362.     break;
  363.  
  364.   case NO_DITHER:
  365.     shmemFlag = 0;
  366.     break;
  367.  
  368.   case ORDERED_DITHER:
  369.     InitColor();
  370.     InitOrderedDither();
  371.     InitDisplay();
  372.     break;
  373.  
  374.   case MONO_DITHER:
  375.   case MONO_THRESHOLD:
  376.     InitMonoDisplay();
  377.     break;
  378.   }
  379.  
  380. #ifdef SH_MEM
  381.     if (shmemFlag && (display != NULL)) {
  382.       if (!XShmQueryExtension(display)) {
  383.     shmemFlag = 0;
  384.     fprintf(stderr, "Shared memory not supported\n");
  385.     fprintf(stderr, "Reverting to normal Xlib.\n");
  386.       }
  387.     }
  388. #endif
  389.  
  390.   if (setjmp(env) != 0) {
  391.  
  392.     DestroyVidStream(theStream);
  393.  
  394.     rewind(input);
  395.  
  396.     EOF_flag = 0;
  397.     curBits = 0;
  398.     bitOffset = 0;
  399.     bufLength = 0;
  400.     bitBuffer = NULL;
  401.     totNumFrames = 0;
  402. #ifdef ANALYSIS 
  403.     init_stats();
  404. #endif
  405.  
  406.   }
  407.  
  408.   theStream = NewVidStream(BUF_LENGTH);
  409.  
  410.  
  411.   mpegVidRsrc(0, theStream);
  412.  
  413.   if (ditherType == Twox2_DITHER) i = 2;
  414.   else i = 1;  
  415.  
  416.   ResizeDisplay(curVidStream->h_size*i, curVidStream->v_size*i);
  417.  
  418.   realTimeStart = ReadSysClock();
  419.  
  420.   while (1) mpegVidRsrc(0, theStream);
  421. }
  422.  
  423.  
  424. /*
  425.  *--------------------------------------------------------------
  426.  *
  427.  * usage --
  428.  *
  429.  *    Print mpeg_play usage
  430.  *
  431.  * Results:
  432.  *    None.
  433.  *
  434.  * Side effects:
  435.  *    exits with a return value -1
  436.  *
  437.  *--------------------------------------------------------------
  438.  */
  439.  
  440. void
  441. usage(s)
  442. char *s;    /* program name */
  443. {
  444.     fprintf(stderr, "Usage:\n");
  445.     fprintf(stderr, "mpeg_play\n");
  446.     fprintf(stderr, "          [-nob]\n");
  447.     fprintf(stderr, "          [-nop]\n");
  448.     fprintf(stderr, "          [-dither {ordered|fs4|fs2|fs2fast|hybrid|hybrid2|2x2|gray|color|none|mono|threshold}]\n");
  449.     fprintf(stderr, "          [-loop]\n");
  450.     fprintf(stderr, "          [-eachstat]\n");
  451. #ifdef AMIGA
  452.     fprintf(stderr, "          [-amiga {window}]\n");
  453. #endif
  454.     fprintf(stderr, "          file_name\n");
  455.     exit (-1);
  456. }
  457.  
  458.  
  459.  
  460. /*
  461.  *--------------------------------------------------------------
  462.  *
  463.  * DoDitherImage --
  464.  *
  465.  *    Called when image needs to be dithered. Selects correct
  466.  *      dither routine based on info in ditherType.
  467.  *
  468.  * Results:
  469.  *    None.
  470.  *
  471.  * Side effects:
  472.  *    None.
  473.  *
  474.  *--------------------------------------------------------------
  475.  */
  476.  
  477. void
  478. DoDitherImage(l, Cr, Cb, disp, h, w) 
  479. unsigned char *l, *Cr, *Cb, *disp;
  480. int h,w;
  481. {
  482.  
  483.   switch(ditherType) {
  484.   case HYBRID_DITHER:
  485.     HybridDitherImage(l, Cr, Cb, disp, h, w);
  486.     break;
  487.  
  488.   case HYBRID2_DITHER:
  489.     HybridErrorDitherImage(l, Cr, Cb, disp, h, w);
  490.     break;
  491.  
  492.   case FS2FAST_DITHER:
  493.     FS2FastDitherImage(l, Cr, Cb, disp, h, w);
  494.     break;
  495.  
  496.   case FS2_DITHER:
  497.     FS2DitherImage(l, Cr, Cb, disp, h, w);
  498.     break;
  499.  
  500.   case FS4_DITHER:
  501.     FS4DitherImage(l, Cr, Cb, disp, h, w);
  502.     break;
  503.  
  504.   case Twox2_DITHER:
  505.     Twox2DitherImage(l, Cr, Cb, disp, h, w);
  506.     break;
  507.  
  508.   case FULL_COLOR_DITHER:
  509.     ColorDitherImage(l, Cr, Cb, disp, h, w);
  510.     break;
  511.  
  512.   case GRAY_DITHER:
  513.     GrayDitherImage(l, Cr, Cb, disp, h, w);
  514.     break;
  515.  
  516.   case NO_DITHER:
  517.     break;
  518.  
  519.   case ORDERED_DITHER:
  520.     OrderedDitherImage(l, Cr, Cb, disp, h, w);
  521.     break;
  522.  
  523.   case MONO_DITHER:
  524.     MonoDitherImage(l, Cr, Cb, disp, h, w);
  525.     break;
  526.  
  527.   case MONO_THRESHOLD:
  528.     MonoThresholdImage(l, Cr, Cb, disp, h, w);
  529.     break;
  530.   }
  531. }
  532.  
  533.  
  534.  
  535.  
  536.